﻿using Beaker;
using Beaker.Injection;
using Beaker.Specs;
using OpenCube.Nbt.Mapping;
using OpenCube.Nbt.Mapping.Converters;

namespace OpenCube.Nbt.Specs.Builders
{
	internal sealed class NbtMapperBuilder<TModel>
		: Builder<NbtMapper<TModel>>
		where TModel : class, new()
	{
		private Maybe<IBuildInConverterFactory> _converterFactory;
		private Maybe<IQueryContainer> _queryContainer;

		public NbtMapperBuilder<TModel> WithQueryContainer(IQueryContainer queryContainer)
		{
			_queryContainer = new Maybe<IQueryContainer>(queryContainer);
			return this;
		}

		public NbtMapperBuilder<TModel> WithConverterFactory(IBuildInConverterFactory converterFactory)
		{
			_converterFactory = new Maybe<IBuildInConverterFactory>(converterFactory);
			return this;
		}

		public override NbtMapper<TModel> Build()
		{
			IQueryContainer queryContainer = _queryContainer.GetValueOrDefault(
				() => new QueryContainerStub());
			IBuildInConverterFactory converterFactory = _converterFactory.GetValueOrDefault(
				new BuildInConverterFactory(queryContainer));
			
			return new NbtMapper<TModel>(converterFactory, queryContainer);
		}
	}
}